/**$Licence:
 *   Use this however/wherever you like, just don't blame me if it breaks anything.
 *
 * Copyright (C) 2008 - 2010 www.java1995.cn . All rights reserved.
 * The webmaster's email:zhuxingsheng@gmail.com
 *
 */
package com.blazemina.core;

import org.apache.commons.lang3.ArrayUtils;
import org.apache.mina.core.service.IoHandlerAdapter;
import org.apache.mina.core.session.IoSession;
import org.apache.mina.filter.codec.demux.MessageDecoder;
import org.apache.mina.util.ExceptionMonitor;

import com.blazegame.logging.Logger;
import com.blazegame.logging.LoggerFactory;
import com.blazemina.AbstractHandler;
import com.blazemina.CommandContext;
import com.blazemina.config.BlazeminaConfigManager;
import com.blazemina.container.RequestProcessor;
import com.blazemina.message.Message;

import flex.messaging.io.amf.ActionMessage;


/**
 * 消息经过Filter处理，到达最后一站，此类把具体处理业务分发给具体处理类
 * 
 * 消息的处理过程：request->decoder->handler->encode->response
 * 
 * <pre>
 * 1、flash发送{@link ActionMessage}-->后台，后台通过消息解码器{@link MessageDecoder}，把二进制流解析为{@link ActionMessage}
 * 2、使用{@link MessageCodcFilter}处理ActionMessage转换成后台业务消息{@link Message}
 * 3、{@link Message}经过{@link MessageCodcFilter},到达{@link ServerHandler}
 * 4、{@link ServerHandler}通过{@link Message}内容，分发给各个service处理具体业务
 * </pre>
 * 
 * 
 * @author JackChu (xingsheng.zhu@gmail.com)
 * @version 1.0 2010-5-22
 */
public class ServerHandler extends AbstractHandler {

	private final static Logger logger = LoggerFactory
			.getLogger(ServerHandler.class);

	public ServerHandler() {
	}

	public void sessionCreated(IoSession ioSession) throws Exception {
	}

	public void messageReceived(final IoSession ioSession, Object msgObj)
			throws Exception {
		final Message message = (Message) msgObj;
		if (logger.isInfoEnabled()) {
			StringBuilder sendMessage = new StringBuilder("session id:"
					+ ioSession.getId() + " receive message,");
			String cmd = message.getCommand();
			sendMessage.append("cmd:" + cmd + " data:");
			Object data = message.getData();
			if (data != null && data.getClass().isArray()) {
				sendMessage.append(ArrayUtils.toString(data));
			} else {
				sendMessage.append(data);
			}
			logger.info(sendMessage.toString());
		}
		RequestProcessor processor = BlazeminaConfigManager.me()
				.getRequestProcessor();

		CommandContext commandContext = new CommandContext() {
			@Override
			public IoSession getSession() {
				return ioSession;
			}

			@Override
			public Message getMessage() {
				return message;
			}
		};
		processor.processor(commandContext);
	}

	public void exceptionCaught(IoSession session, Throwable cause)
			throws Exception {
		session.close(true);
		ExceptionMonitor.getInstance().exceptionCaught(cause);
	}

	public void messageSent(IoSession session, Object message) throws Exception {
		if (logger.isInfoEnabled()) {

			StringBuilder sendMessage = new StringBuilder("session id:"
					+ session.getId() + " send message,");
			if (message instanceof Message) {
				Message msg = (Message) message;
				String cmd = msg.getCommand();
				sendMessage.append("cmd:" + cmd + " data:");
				Object data = msg.getData();
				if (data != null && data.getClass().isArray()) {
					sendMessage.append(ArrayUtils.toString(data));
				} else {
					sendMessage.append(data);
				}
			} else {
				sendMessage.append("is not Message object");
			}
			logger.info(sendMessage.toString());
		}
	}
}
